﻿using System;
using System.Collections.Generic;
using System.Linq;

using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework;

namespace WorldOnFire
{
    public class CSkybox
    {
        public static CRenderingManager s_RenderingManager;

        // The list of texture sets the skybox can use
        public enum eTextureSet
        {
            GREEN_NOVA,
            RAINBOW_STUFF,
            COUNT
        }

        // The texture set the skybox is using
        //private eTextureSet m_eTextureSet;
        private Texture2D[] m_StevesTextures;

        // The texture IDs from the rendering manager
        //private CRenderingManager.eTextureID[] m_eTextureIDs;

        // The skybox model
        private Model m_Model;
        private Matrix[] m_mBoneTransforms;

        public void Initialize(ContentManager _ContentManager)
        {
            // Load the skybox
            m_Model = _ContentManager.Load<Model>("Skybox/Steve The Skybox");
            m_mBoneTransforms = new Matrix[m_Model.Bones.Count];
            m_Model.CopyAbsoluteBoneTransformsTo(m_mBoneTransforms);

            // TODO: DIE DIE DIE
            m_StevesTextures = new Texture2D[6];
            m_StevesTextures[0] = _ContentManager.Load<Texture2D>("Skybox/skybox_DN");
            m_StevesTextures[1] = _ContentManager.Load<Texture2D>("Skybox/skybox_BK");
            m_StevesTextures[2] = _ContentManager.Load<Texture2D>("Skybox/skybox_RT");
            m_StevesTextures[3] = _ContentManager.Load<Texture2D>("Skybox/skybox_LF");
            m_StevesTextures[4] = _ContentManager.Load<Texture2D>("Skybox/skybox_UP");
            m_StevesTextures[5] = _ContentManager.Load<Texture2D>("Skybox/skybox_FR");
        }

        public void Render(GraphicsDevice _GraphicsDevice)
        {
            // Get the effect from the rendering manager
            Effect ObjectEffect = s_RenderingManager.GetEffect(CRenderingManager.eEffectID.SKYBOX);

            // TODO: WHAT THE FUCK IS THIS? JESUS.
            DepthStencilState NotSteve = _GraphicsDevice.DepthStencilState;

            DepthStencilState Steve = new DepthStencilState();
            Steve.DepthBufferEnable = false;
            _GraphicsDevice.DepthStencilState = Steve;

            // Loop through each mesh
            for (int iMesh = 0; iMesh < m_Model.Meshes.Count; ++iMesh)
            {
                // Store the mesh locally
                ModelMesh Mesh = m_Model.Meshes[iMesh];

                // Set the world transform
                ObjectEffect.Parameters["g_mWorld"].SetValue(m_mBoneTransforms[Mesh.ParentBone.Index]);

                // Set the texture
                ObjectEffect.Parameters["g_Texture"].SetValue(m_StevesTextures[iMesh]);

                // Loop through each mesh part
                foreach (ModelMeshPart MeshPart in Mesh.MeshParts)
                {
                    // Set the vertex buffer
                    _GraphicsDevice.SetVertexBuffers(
                        new VertexBufferBinding(MeshPart.VertexBuffer, MeshPart.VertexOffset, 0));

                    // Set the index buffer
                    _GraphicsDevice.Indices = MeshPart.IndexBuffer;

                    // Loop through each pass
                    foreach (EffectPass Pass in ObjectEffect.CurrentTechnique.Passes)
                    {
                        // Begin the pass
                        Pass.Apply();

                        // Draw magic things
                        _GraphicsDevice.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0,
                            MeshPart.NumVertices, MeshPart.StartIndex, MeshPart.PrimitiveCount);
                    }
                }
            }

            //DepthStencilState NotSteve = new DepthStencilState();
            _GraphicsDevice.DepthStencilState = NotSteve;
        }
    }
}
